package com.qianfeng.smsplatform.service.impl;

//
//                            _ooOoo_  
//                           o8888888o  
//                           88" . "88  
//                           (| -_- |)  
//                            O\ = /O  
//                        ____/`---'\____  
//                      .   ' \\| |// `.  
//                       / \\||| : |||// \  
//                     / _||||| -:- |||||- \  
//                       | | \\\ - /// | |  
//                     | \_| ''\---/'' | |  
//                      \ .-\__ `-` ___/-. /  
//                   ___`. .' /--.--\ `. . __  
//                ."" '< `.___\_<|>_/___.' >'"".  
//               | | : `- \`.;`\ _ /`;.`/ - ` : | |  
//                 \ \ `-. \_ __\ /__ _/ .-` / /  
//         ======`-.____`-.___\_____/___.-`____.-'======  
//                            `=---='  
//  
//         .............................................  
//                  佛祖镇楼                  BUG辟易  
//          佛曰:  
//                  写字楼里写字间，写字间里程序员；  
//                  程序人员写程序，又拿程序换酒钱。  
//                  酒醒只在网上坐，酒醉还来网下眠；  
//                  酒醉酒醒日复日，网上网下年复年。  
//                  但愿老死电脑间，不愿鞠躬老板前；  
//                  奔驰宝马贵者趣，公交自行程序员。  
//                  别人笑我忒疯癫，我笑自己命太贱；  
//  


import com.qianfeng.smsplatform.api.CacheService;
import com.qianfeng.smsplatform.common.constants.CacheConstants;
import com.qianfeng.smsplatform.common.constants.ResutlDataEnum;
import com.qianfeng.smsplatform.common.model.Standard_Submit;
import com.qianfeng.smsplatform.exception.MyBaseException;
import com.qianfeng.smsplatform.service.ISmsCheckService;
import com.qianfeng.smsplatform.service.PushSubmitToQueueService;
import com.qianfeng.smsplatform.utils.PhoneFormatCheckUtil;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.DigestUtils;
import org.springframework.util.StringUtils;

import java.nio.charset.StandardCharsets;
import java.util.*;
import java.util.stream.Collectors;

/**
 * Created by Jackiechan on 2021/9/3/20:29
 *
 * @author Jackiechan
 * @version 1.0
 * @since 1.0
 */
@Service
public class SmsCheckServiceImpl implements ISmsCheckService {


    private CacheService cacheService;

    private PushSubmitToQueueService pushSubmitToQueueService;

    @Autowired
    public void setPushSubmitToQueueService(PushSubmitToQueueService pushSubmitToQueueService) {
        this.pushSubmitToQueueService = pushSubmitToQueueService;
    }

    @Autowired
    public void setCacheService(CacheService cacheService) {
        this.cacheService = cacheService;
    }

    @Override
    public   List<String> checkSms(String clientId, String pwd, String content, String mobile, String srcId, String ip) {
        //检查账号密码,内容,手机号码,唯一id,ip是不是符合我们的要求
        if (StringUtils.isEmpty(clientId) || StringUtils.isEmpty(pwd) || StringUtils.isEmpty(content) || StringUtils.isEmpty(mobile) || StringUtils.isEmpty(srcId) || StringUtils.isEmpty(ip)) {
            //参数不完整,需要检查参数,等会我们想想通过什么返回给用户返回结果
            throw new MyBaseException(ResutlDataEnum.PARAMSERROR);
        }
        if (content.length() > 500) {//短信的限制长度应该可以通过管理平台修改
            //短信内容过长,不允许发送
            throw new MyBaseException(ResutlDataEnum.MESSAGECONTENTERROR);
        }
        //现在我们处理的是一个手机号,实际上我们可以允许用户一次性向不同的手机号发送想用的内容
//        if (!PhoneFormatCheckUtil.isPhoneLegal(mobile)) {
//            //手机号不符合要求
//            throw new MyBaseException(ResutlDataEnum.MOBILENUMERROR);
//        }
        String[] mobiles = mobile.split(",");//很多个手机号
        List<String> okMobiles = Arrays.stream(mobiles).filter(mob -> PhoneFormatCheckUtil.isPhoneLegal(mob)).collect(Collectors.toList());
        List<String> failMobile = Arrays.stream(mobiles).filter(mob -> !PhoneFormatCheckUtil.isPhoneLegal(mob)).collect(Collectors.toList());

        //将发送方的唯一序号转为long
        long srccode;
        try {
            srccode = Long.parseLong(srcId);//转换发送方的id
        } catch (Exception e) {
            e.printStackTrace();
            throw new MyBaseException(ResutlDataEnum.SRCIDERROR);
        }

        //符合手机号的要求,继续下一步
        Map map = cacheService.hmget(CacheConstants.CACHE_PREFIX_CLIENT + clientId);
        if (map != null && map.size() > 0) {
            //判断用户信息,需要查询缓存
            String ipaddress = (String) map.get("ipaddress");//获取到允许的来源ip,发送请求的服务器ip必须来自于这个ip内
            if (!ipaddress.contains(ip)) {
                //说明你的ip不在允许的ip内,应该拦截
                //TODO 拦截操作,就是返回结果
                throw new MyBaseException(ResutlDataEnum.IPERROR);
            }
            //账号和密码呢(其实就只有密码)
            //假如此处我们就只用MD5做了一个简单的校验,没有使用复杂的盐等
            String realPwd = (String) map.get("pwd");
            //将传递的密码转成MD5
            String pwdMD5 = DigestUtils.md5DigestAsHex(pwd.getBytes(StandardCharsets.UTF_8));
            if (!pwdMD5.equalsIgnoreCase(realPwd)) {
                //密码校验失败,通知用户
                //通知用户
                throw new MyBaseException(ResutlDataEnum.PWDERROR);
            }

            if (okMobiles.size()>0) {//遍历每一个手机号,理论上我们最多允许一次发送1000个手机号, 也就是这个ok的手机集合的长度不能大鱼1000,当然这个区域于我们的业务
                List<Standard_Submit> standard_submitList = new ArrayList<>();
                for (String mob : okMobiles) {
                    //等上面的校验都完成了,代表没有问题,可以发送信息
                    Standard_Submit standard_submit = new Standard_Submit();
                    standard_submit.setDestMobile(mob);
                    standard_submit.setClientID(Integer.parseInt(clientId));
                    standard_submit.setMessageContent(content);
                    standard_submit.setSrcSequenceId(srccode);
                    standard_submit.setSendTime(new Date());
                    standard_submit.setSource((Integer) map.get("usertype"));
                    standard_submitList.add(standard_submit);
                }
                pushSubmitToQueueService.sendSubmittoQueue(standard_submitList);
            }

        } else {
            //代表没有获取到客户信息,可能是客户id错误
            throw new MyBaseException(ResutlDataEnum.CLIENTIDERROR);
        }

        return failMobile;
    }
}
